home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
C/C++ Users Group Library 1996 July
/
C-C++ Users Group Library July 1996.iso
/
vol_100
/
102_01
/
bg.c
< prev
next >
Wrap
Text File
|
1984-02-10
|
19KB
|
786 lines
/*
Backgammon...finally, some"one" else to play against than just
my girlfriend, who hates to lose! (but then, so do I...and this
program doesn't do too bad a job at keeping me honest)
Modified for BDS C by Leor Zolman, 2/82
*/
#include <bdscio.h>
#define H19 1 /* true if to be run on H19 terminal */
#define NIL (-1)
#define MAXGMOV 10
#define MAXIMOVES 1000
char level; /*'b'=beginner, 'i'=intermediate, 'e'=expert*/
int die1;
int die2;
int i;
int j;
int l;
int m;
int count;
int red[31];
int white[31];
int probability[13];
int imoves;
int goodmoves[MAXGMOV];
int probmoves[MAXGMOV];
struct {
int pos[4];
int mov[4];
} moves[MAXIMOVES];
exinit()
{
int i;
setmem(externs(), endext() - externs(), 0);
red[1] = white[1] = 2;
red[12] = white[12] = 5;
red[17] = white[17] = 3;
red[19] = white[19] = 5;
probability[0] = 0;
probability[1] = 11;
probability[2] = 12;
probability[3] = 13;
probability[4] = 14;
probability[5] = 15;
probability[6] = 16;
probability[7] = 6;
probability[8] = 5;
probability[9] = 4;
probability[10] = 3;
probability[11] = 2;
probability[12] = 1;
}
main()
{
int t,k,n,go[5];
char c, s[MAXLINE];
int i;
int first; /* true on first move only */
int mywins, hiswins;
printf("\n\nWelcome to BACKGAMMON!\n");
nrand (0,"Do you need instructions? ");
if(tolower(getchar())=='y')
instructions();
else puts("\n\n");
mywins = hiswins = 0;
printf( "Choose the level of your oppponent:\n");
printf( "Type 'b' for beginner, or 'i' for intermediate,\n");
printf( "or anything else to play an expert... ?");
level='e';
if((c = tolower(getchar()))=='b') level='b';
else if(c=='i') level='i';
printf( "\n\nI'll play white, and you'll play red.\n\n");
newgame:
exinit();
first = 1;
go[5]=NIL;
printf("Let's throw the dice to see who goes first:\n");
throw: roll();
printf("I throw: ");
sleep(15);
printf("%d, and you throw: ",die1);
sleep(15);
printf("%d ... ",die2);
sleep(15);
if (die1 == die2) {
printf("Tied up, so let's try again:\n");
goto throw;
}
printf("%s go first...\n\n", die1 > die2 ? "I" : "You");
if (die2 > die1) goto nowhmove;
whitesmv:
if (!first) roll(); /* skip roll on first move */
order();
first = 0; /* after this, not first roll anymore */
#if H19
printf( "\nWhite rolls \33p %d,%d \33q... ",die1,die2);
#else
printf( "\nWhite rolls %d,%d ... ",die1,die2);
#endif
if (!chkmov(white,red)) {
printf("White has no moves. Foo.\n");
goto nowhmove;
}
printf( "White's move is: ");
if(nextmove(white,red)==NIL)goto nowhmove;
if(piececount(white,0,24)==0) {
printf( "\7White wins!\n");
printf("\nGame score: Me: %d, You: %d\n",++mywins,hiswins);
if (mywins == hiswins)
printf("All tied up! Who's gonna pull ahead?\n");
else if (mywins > 2 && !hiswins)
printf ("It's about time you managed to win a game!\n");
else switch(nrand(1) % 5) {
case 4:
case 0: printf("Aren't you ashamed? You've been beaten ");
printf("by a computer...\n");
break;
case 1: printf("Not bad for a dumb program, eh?\n");
break;
case 2: printf("Better luck next time, sucker....\n");
break;
case 3: printf("Maybe you'd better stick to checkers?\n");
break;
}
goto again;
}
nowhmove:
prtbrd();
if (!first) roll(); /* skip roll on first move */
first = 0; /* after this, not 1st roll anymore */
retry:
order();
#if H19
printf( "Your roll is \33p %d, %d \33q ... ",die1,die2);
#else
printf( "Your roll is %d,%d ... ",die1,die2);
#endif
if (!chkmov(red,white)) {
printf("Sorry, you have no possible moves.\n");
printf("Type any key to let me make my next move: ");
getchar();
goto whitesmv;
}
printf("your move? ");
while (!kbhit()) nrand(1); /* Exercize the random generator while */
gets(s); /* waiting for a move to be made... */
if (ignore_sp(s) == '?' || ignore_sp(s) == 'h') {
puts("\nType either a list of moves, separated by spaces, or:\n");
puts(" q -- to quit the current game\n");
puts(" b -- to see the board\n");
puts(" ? -- to see these options (h does the same thing)\n");
puts("Do you want to see the long instructions? ");
if (tolower(getchar()) == 'y') instructions();
puts("\n");
goto retry;
}
if (ignore_sp(s) == 'q') { /* check for quit command */
puts("Are you sure you want to quit? ");
if (tolower(getchar()) == 'y') goto again;
putchar('\n');
goto retry;
}
if (ignore_sp(s) == 'b') { /* check for print board command */
prtbrd();
goto retry;
}
/* check for null move */
if( ignore_sp(s) != '-' && !isdigit(ignore_sp(s))) {
printf("You MUST make a move!\n");
goto retry;
}
for (i = 0; s[i]; i++) /* convert commas to spaces */
if (s[i] == ',') s[i] = ' ';
n=sscanf(s,"%d%d%d%d%d",&go[0],&go[1],&go[2],&go[3],&go[4]);
if( (die1 != die2 && n > 2) || n > 4) {
printf( "You've made too many moves;\n");
goto retry;
}
if( ((die1 != die2) && n < 2) || ((die1 == die2) && n < 4)) {
if (n == cntred()) goto moveok;
printf("Are you sure you can't make all the moves? ");
if (tolower(getchar()) != 'y') {
printf("\nOK, then let's try it again:\n");
goto retry;
}
putchar('\n');
}
moveok: go[n]=NIL;
if(*s=='-'){
go[0]= -go[0];
t=die1;
die1=die2;
die2=t;
}
for(k=0; k<n; k++) {
if(0<=go[k] && go[k]<=24)continue;
else{
printf( "Sorry, move %d is illegal.\n",go[k]);
goto retry;
}
}
if(play(red,white,go))goto retry;
if(piececount(red,0,24)==0){
printf( "\n\7Red wins.\n");
printf("\nGame score: Me: %d, You: %d\n",mywins,++hiswins);
if (mywins == hiswins)
printf("Looks like now we're dead even...tiebreaker time!\n");
else if (hiswins > 2 && !mywins)
printf("See? I'm not THAT stupid after all!\n");
else switch(nrand(1) % 5) {
case 0: printf( "Congratulations! You've just defeated a ");
printf( "dumb machine.\n");
break;
case 1: printf("Sigh...at least I put up a good fight, eh?\n");
break;
case 2: printf("Darn....I'll get you next time, human!\n");
break;
case 3: printf("Mumble...those unlucky rolls will do it ");
printf("every time!\n");
break;
case 4: printf("Not bad... for a dumb human!\n");
}
again: printf("\nWould you like to play another game? ");
if (tolower(getchar()) != 'y') exit();
printf("\n\n");
goto newgame;
}
goto whitesmv;
}
char ignore_sp(s) /* return first non-whitespace char at s: */
char *s;
{
char c;
while (isspace(c = *s++));
return tolower(c);
}
play(player,playee,pos)
int *player,*playee,pos[];
{
int k,n,die,ipos;
for(k=0;k<player[0];k++){ /*blots on player[0] must be moved first*/
if(pos[k]==NIL)break;
if(pos[k]!=0){
printf( "\nPiece on BAR (position 0) must be moved first\n");
return(-1);
}
}
for(k=0;(ipos=pos[k])!=NIL;k++){
die=k?die2:die1;
n=25-ipos-die;
if(player[ipos]==0)goto badmove;
if(n>0 && playee[n]>=2)goto badmove;
if(n<=0){
if(piececount(player,0,18)!=0)goto badmove;
if((ipos+die)!=25 &&
piececount(player,19,24-die)!=0)goto badmove;
}
player[ipos]--;
player[ipos+die]++;
}
for(k=0;pos[k]!=NIL;k++){
die=k?die2:die1;
n=25-pos[k]-die;
if(n>0 && playee[n]==1){
playee[n]=0;
playee[0]++;
}
}
return(0);
badmove:
printf( "Move %d is not legal. Enter all moves again:\n",ipos);
while(k--){
die=k?die2:die1;
player[pos[k]]++;
player[pos[k]+die]--;
}
prtbrd();
return(-1);
}
cntred() /* count up number of red's pieces */
{
int i, count;
for (count = 0, i = 0; i < 25; i++) count += red[i];
return count;
}
chkmov(player,playee) /* return true if player has possible move */
int *player, *playee;
{
int k;
imoves=0;
movegen(player,playee);
if(die1!=die2) {
k = die1; die1 = die2; die2 = k;
movegen(player,playee);
k = die1;